package addon.w3.w3x;

import java.awt.Color;
import java.awt.Frame;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.EOFException;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

import chaos.util.CMPQResourceManager;

import com.jme.bounding.BoundingBox;
import com.jme.math.Vector3f;
import com.jme.scene.Node;

import natv.CoreNative;

import addon.w3.mdx.LEDataInputStream;
import addon.w3.mdx.MDXToJme;

public class W3XReader {
	String mapFile;
	FileInputStream fin;
	LEDataInputStream lein;
	
	CMPQResourceManager cman;
	W3XEnvironment w3xenv;
	W3XDoodad w3xdoo;
	W3XPathMap w3xpath;
	
	public W3XReader(String mapFile) throws FileNotFoundException {
		this.mapFile = mapFile;
		streamReset();
	}
	
	protected void streamReset() throws FileNotFoundException {
		try {
			fin.close();
		} catch (Exception e) {
			// TODO: handle exception
		}
		fin = new FileInputStream(mapFile);
		lein = new LEDataInputStream(fin);
	}
	
	protected void debug(String msg) {
		System.out.println(msg);
	}
	
	public CMPQResourceManager getCMan() {
		return cman;
	}
	
	public W3XEnvironment getW3XEnv() {
		return w3xenv;
	}
	
	public W3XDoodad getW3XDoodad() {
		return w3xdoo;
	}
	
	public W3XPathMap getW3XPathMap() {
		return w3xpath;
	}
	
	public void parse() throws W3XException, IOException {
		String tag = readString(4);
		if(tag.equals("HM3W")) {
			//throw new W3XException("w3x map correct");
		} else {
			throw new W3XException("invalid .w3x");
		}
		int tempInt = readInt();
		String mapName = readString();
		
		int mapFlag = readInt();
		checkFlag(mapFlag);
		int playernum = readInt();
		
		makeTempW3X();
		
		
		try {
			cman = new CMPQResourceManager( new File("").getAbsolutePath()+"\\cbf_temp.mpq" );
			cman.init();
		} catch (Exception e) {
		}
		
		byte data[] = CoreNative.singleton().getFileDataFromCustomMPQ("war3map.w3e".getBytes());
		
		w3xenv = new W3XEnvironment(data);
		w3xenv.decode();
		fin.close();
		
		data = CoreNative.singleton().getFileDataFromCustomMPQ("war3map.doo".getBytes());
		w3xdoo = new W3XDoodad(data);
		w3xdoo.decode();
		
		data = CoreNative.singleton().getFileDataFromCustomMPQ("war3map.wpm".getBytes());
		w3xpath = new W3XPathMap(data);
		w3xpath.decode();
	}
	
	protected void makeTempW3X() throws IOException {
		streamReset();
		lein.skip(512);
		FileOutputStream fos = new FileOutputStream("cbf_temp.mpq");
		byte data[] = new byte[1024];
		while(true) {
			if(lein.available() < data.length) {
				data = new byte[lein.available()];
				lein.read(data);
				fos.write(data);
				break;
			}
			int readed = lein.read(data);
			fos.write(data, 0, readed);
		}
		fos.flush();
		fos.close();
	}
	
	public void checkFlag(int flag) {
//		0x0001: if 1=hide minimap in preview screens
//		0x0002: if 1=modify ally priorities
//		0x0004: if 1=melee map
//		0x0008: if 1=playable map size was large and has never been reduced to medium
//		0x0010: if 1=masked area are partially visible
//		0x0020: if 1=fixed player setting for custom forces
//		0x0040: if 1=use custom forces
//		0x0080: if 1=use custom techtree
//		0x0100: if 1=use custom abilities
//		0x0200: if 1=use custom upgrades
//		0x0400: if 1=map properties menu opened at least once since map creation
//		0x0800: if 1=show water waves on cliff shores
//		0x1000: if 1=show water waves on rolling shores
//		int: max number of players

//		if( (flag&0x0001) == 0x0001) {
//			System.out.println("hide minimap in preview screens");
//		} else if( (flag&0x0002) == 0x0002) {
//			System.out.println("modify ally priorities");
//		} else if( (flag&0x0004) == 0x0004) {
//			System.out.println("melee map");
//		} else if( (flag&0x0008) == 0x0008) {
//			System.out.println("playable map size was large and has never been reduced to medium");
//		} else if( (flag&0x0010) == 0x0010) {
//			System.out.println("masked area are partially visible");
//		} else if( (flag&0x0020) == 0x0020) {
//			System.out.println("fixed player setting for custom forces");
//		} else if( (flag&0x0040) == 0x0040) {
//			System.out.println("use custom forces");
//		} else if( (flag&0x0080) == 0x0080) {
//			System.out.println("use custom techtree");
//		} else if( (flag&0x0100) == 0x0100) {
//			System.out.println("use custom abilities");
//		} else if( (flag&0x0200) == 0x0200) {
//			System.out.println("use custom upgrades");
//		} else if( (flag&0x0400) == 0x0400) {
//			System.out.println("map properties menu opened at least once since map creation");
//		} else if( (flag&0x0800) == 0x0800) {
//			System.out.println("show water waves on cliff shores");
//		} else if( (flag&0x1000) == 0x1000) {
//			System.out.println("show water waves on rolling shores");
//		}
	}
	
	public String readString(int len) throws IOException {
		byte temp[] = new byte[len];
		lein.read(temp);
		String tag = new String(temp);
		return tag;
	}
	
	public String readString() throws IOException {
		ByteArrayOutputStream bos = new ByteArrayOutputStream();
		do {
			byte b = lein.readByte();
			if(b == 0) break;
			bos.write(b);
		} while(true);
		return new String(bos.toByteArray(),"utf8");
	}
	
	public int readInt() throws EOFException, IOException {
		return lein.readInt();
	}
	
	
	public static void main(String args[]) {
		try {
			W3XReader mapReader = new W3XReader("chaos.w3x");
			mapReader.parse();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}